package lab3;
import java.io.BufferedReader;
import java.io.FileReader;
import java.io.IOException;
import java.util.ArrayList;
import java.util.Set;
import java.util.StringTokenizer;
import java.util.TreeMap;

public class WordCount {
	
	public static class SetOfWords{
		public TreeMap<String, Integer> set= new TreeMap<String, Integer>();
		public synchronized void addWord(String word, Integer count){			
			if (set.containsKey(word)){
				set.put(word, set.get(word)+count);
			}else{
				set.put(word, count);
			}			
		}
	}
	
	public static Worker[] threads;
	
	public static int findFreeThread(int countOfThreads){
		int i=0;
		while(true){
			//System.out.println(i+" "+threads[i].isAlive());
			if (!threads[i].isRun){
				return i;
			}
			if (i==countOfThreads-1){
				i=0;
			}else{
				i++;
			}			
		}
	}
	
	public static SetOfWords setWords=new SetOfWords();
	public static boolean endOfFile=false;
	
	public static class Worker extends Thread{
		public ArrayList<String> str=new ArrayList<String>();
		public SetOfWords tempSetWords= new SetOfWords();
		public boolean isRun=true;
		public void run(){
			do{
				if (isRun){
					tempSetWords.set.clear();
					for (int j=0; j<str.size(); j++){
						String s=str.get(j);
              StringTokenizer st=new StringTokenizer(s, " \t\n\r,.:!?;'\"()[]{}");
						while(st.hasMoreTokens()){	
							String s1=st.nextToken();
							s1=s1.toLowerCase();
							tempSetWords.addWord(s1, 1);
						}
					}
					for (String s : tempSetWords.set.keySet()){
						setWords.addWord(s, tempSetWords.set.get(s));
					}
					str.clear();
					isRun=false;
				}
				if (endOfFile){
					return;
				}
				try {
					Thread.sleep(10);
				} catch (InterruptedException e) {}
			}while(true);
		}
	}

	public static void main(String[] args) throws IOException {		
		BufferedReader in= null;
		int countOfThreads;
		try{
			if (args.length==2){
				in=new BufferedReader(new FileReader(args[0]));
				countOfThreads=Integer.parseInt(args[1]);	
			}else{
				System.out.println("Usage: ");
				System.out.println("lab <input> <count of Threads>");
				return;
			}
			threads=new Worker[countOfThreads];			
			for (int i=0; i<countOfThreads; i++){
				threads[i]=new Worker();
			}
			String input = in.readLine();
			int id=0;
			for(int i=0; i<countOfThreads; i++){
				threads[i].start();
			}
			while (input!=null){
				id=findFreeThread(countOfThreads);
				for (int i=0; i<10; i++){
					if (input==null) break;
					threads[id].str.add(input);
					input=in.readLine();
				}
				threads[id].isRun=true;		
			}
			endOfFile=true;
			for(int i=0; i<countOfThreads; i++){
				try{
					threads[i].join();
				}catch(InterruptedException e){
					System.out.println("The thread was interrupted");
					return;
				}
			}
			System.out.println("Word -> Number of repeats");
			for (String s : setWords.set.keySet())
				System.out.println(s+" -> "+setWords.set.get(s));
			//System.out.println(setWords.set);
		}finally{
			try{
			if (in!=null) in.close();	
			}catch(IOException e){
				System.out.println(e.toString());
			}
		}
		

	}

}
